package pe.com.rimac.portal.facturacion.handler.impl;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;

import pe.com.rimac.portal.facturacion.handler.ListHandler;
import pe.com.rimac.portal.facturacion.handler.SearchCriteria;
import pe.com.rimac.portal.facturacion.modelo.Factura;
import pe.com.rimac.portal.facturacion.servicio.AseguradoService;

/**
 * Implementaci&oacute;n con funcionalidad base para {@link ListHandler}
 * 
 * @author Andres Deza Villacorta - Synopsis S.A
 * 
 */
public abstract class BaseListHandler implements ListHandler
{
	@Autowired
	protected AseguradoService aseguradoService;
	protected List<Factura> results;
	protected SearchCriteria searchCriteria;
	protected int pageSize = 0;
	protected int currentIndex = 0;

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#executeSearch()
	 */
	public abstract void executeSearch();

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#markAll()
	 */
	public abstract void markAll();

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#unmarkAll()
	 */
	public abstract void unmarkAll();

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#mark(java.lang.String)
	 */
	public abstract void mark(String numeroFactura);

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getSelected(java.lang.String)
	 */
	public abstract Factura getSelected(String numero);

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getMarkedElements()
	 */
	public abstract List<Factura> getMarked();

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getMarkedForExport(boolean)
	 */
	public abstract List<Factura> getMarkedForExport(boolean isPDF);

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getSearchCriteria()
	 */
	public SearchCriteria getSearchCriteria()
	{
		return searchCriteria;
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#setSearchCriteria(pe.com.rimac.portal.facturacion.handler.SearchCriteria)
	 */
	public void setSearchCriteria(SearchCriteria searchCriteria)
	{
		this.searchCriteria = searchCriteria;
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getListSize()
	 */
	public int getListSize()
	{
		return results.size();
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getList()
	 */
	public List<Factura> getList()
	{
		return Collections.unmodifiableList(results);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getPageSize()
	 */
	public int getPageSize()
	{
		return pageSize;
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#setPageSize(int)
	 */
	public void setPageSize(int size)
	{
		this.pageSize = size;
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getPagesCount()
	 */
	public int getPagesCount()
	{
		if (results.size() == 0)
		{
			return 0;
		}
		else if (pageSize == 0)
		{
			return 1;
		}
		else
		{
			return (int) Math.ceil(results.size() / (pageSize * 1.0));
		}
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getFirstPage()
	 */
	public List<Factura> getFirstPage()
	{
		return getPage(0);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getLastPage()
	 */
	public List<Factura> getLastPage()
	{
		return getPage(getPagesCount() - 1);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getNextPage()
	 */
	public List<Factura> getNextPage()
	{
		return getPage(currentIndex + 1);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getPreviousPage()
	 */
	public List<Factura> getPreviousPage()
	{
		return getPage(currentIndex - 1);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getCurrentPage()
	 */
	public List<Factura> getCurrentPage()
	{
		return getPage(currentIndex);
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getCurrentIndex()
	 */
	public int getCurrentIndex()
	{
		return currentIndex;
	}

	/**
	 * @see pe.com.rimac.portal.facturacion.handler.ListHandler#getPage(int)
	 */
	public List<Factura> getPage(int page)
	{
		if (page < 0 || page >= getPagesCount())
		{
			throw new IndexOutOfBoundsException();
		}
		int fromIndex = page * pageSize;
		int toIndex = fromIndex + pageSize;
		if (toIndex > results.size())
		{
			toIndex = results.size();
		}
		currentIndex = page;
		// subList puede devolver un RandomAccessSubList, el cual no es serializable
		// hacemos un copia a ArrayList
		return Collections.unmodifiableList(new ArrayList<Factura>(results.subList(fromIndex, toIndex)));
	}
}